package bma.common.netty;

import java.nio.charset.Charset;
import java.util.Set;

import org.jboss.netty.buffer.ChannelBuffer;
import org.jboss.netty.buffer.ChannelBuffers;
import org.jboss.netty.channel.Channel;
import org.jboss.netty.channel.ChannelFuture;
import org.jboss.netty.channel.ChannelFutureListener;
import org.jboss.netty.handler.codec.http.Cookie;
import org.jboss.netty.handler.codec.http.CookieDecoder;
import org.jboss.netty.handler.codec.http.CookieEncoder;
import org.jboss.netty.handler.codec.http.DefaultHttpResponse;
import org.jboss.netty.handler.codec.http.HttpHeaders;
import org.jboss.netty.handler.codec.http.HttpMethod;
import org.jboss.netty.handler.codec.http.HttpRequest;
import org.jboss.netty.handler.codec.http.HttpResponse;
import org.jboss.netty.handler.codec.http.HttpResponseStatus;
import org.jboss.netty.util.CharsetUtil;

public class NettyHttpUtil {

	public static void sendResponse(Channel ch, HttpRequest request,
			HttpResponseStatus status, String msg) {
		HttpResponse response = new DefaultHttpResponse(
				request.getProtocolVersion(), status);
		if (msg != null) {
			response.setContent(ChannelBuffers.copiedBuffer(msg,
					CharsetUtil.UTF_8));
		}
		sendResponse(ch, request, response);
	}

	public static void sendResponse(Channel ch, HttpRequest request,
			HttpResponse response) {
		if (!ch.isOpen()) {
			return;
		}

		ChannelBuffer content = response.getContent();
		if (content == null) {
			// skip
			if (response.getStatus().getCode() != 200) {
				response.setContent(ChannelBuffers.copiedBuffer(response
						.getStatus().toString(), CharsetUtil.UTF_8));
				HttpHeaders.setContentLength(response, response.getContent()
						.readableBytes());
			}
		}

		// Send the response and close the connection if necessary.
		ChannelFuture f = ch.write(response);
		if (!HttpHeaders.isKeepAlive(request)
				|| response.getStatus().getCode() != 200) {
			f.addListener(ChannelFutureListener.CLOSE);
		}

	}

	public static HttpResponse createResponse(HttpRequest request,
			boolean withCookie) {
		HttpResponse response = new DefaultHttpResponse(
				request.getProtocolVersion(), HttpResponseStatus.OK);
		if (withCookie) {
			// Encode the cookie.
			String cookieString = request.getHeader(HttpHeaders.Names.COOKIE);
			if (cookieString != null) {
				CookieDecoder cookieDecoder = new CookieDecoder();
				Set<Cookie> cookies = cookieDecoder.decode(cookieString);
				if (!cookies.isEmpty()) {
					// Reset the cookies if necessary.
					CookieEncoder cookieEncoder = new CookieEncoder(true);
					for (Cookie cookie : cookies) {
						cookieEncoder.addCookie(cookie);
					}
					response.addHeader(HttpHeaders.Names.SET_COOKIE,
							cookieEncoder.encode());
				}
			}
		}
		return response;
	}

	public static String getCharset(HttpRequest request) {
		String contentType = request.getHeader("Content-Type");
		if (contentType == null) {
			return null;
		}
		int idx = contentType.indexOf("charset");
		if (idx == -1 && idx + 8 < contentType.length()) {
			return null;
		}
		return contentType.substring(idx + 8).trim();
	}

	public static Charset getCharset(HttpRequest httpRequest, Charset def) {
		String s = getCharset(httpRequest);
		if (s == null)
			return def;
		try {
			return Charset.forName(s);
		} catch (Exception e) {
			return def;
		}
	}

	public static final boolean isMultipartContent(HttpRequest request) {
		if (HttpMethod.POST != request.getMethod()) {
			return false;
		}
		String contentType = request.getHeader("Content-Type");
		if (contentType == null) {
			return false;
		}
		if (contentType.toLowerCase().startsWith("multipart/")) {
			return true;
		}
		return false;
	}
}
